﻿using System.Timers;
using System.Windows;
using System.Windows.Input;

namespace Xioa_UI.Service;

public class WindowMoveSizeChange
{
    private WindowMoveSizeChange()
    {
    }

    #region WindowStateMaximizedAction

    private event Action? WindowStateMaximizedAction;

    private Dictionary<string, Action> _maximizedActions = new Dictionary<string, Action>();

    public void AddWindowStateMaximizedAction(string key, Action action)
    {
        if (_maximizedActions.TryGetValue(key, out var havingAction))
        {
            throw new Exception("Key Value Is Having");
        }

        _maximizedActions.Add(key, action);
        this.WindowStateMaximizedAction += action;
    }

    public void DelWindowStateMaximizedAction(string key)
    {
        if (_maximizedActions.TryGetValue(key, out var action))
        {
            this.WindowStateMaximizedAction -= action;
            this._maximizedActions.Remove(key);
        }
        else
        {
            throw new Exception("Not Found Key");
        }
    }

    public void ClearWindowStateMaximizedAction()
    {
        foreach (var item in _maximizedActions)
        {
            this.WindowStateMaximizedAction -= item.Value;
        }
    }

    #endregion

    #region WindowStateNormalAction

    private event Action? WindowStateNormalAction;

    private Dictionary<string, Action> _normalActions = new Dictionary<string, Action>();

    public void AddWindowStateNormalAction(string key, Action action)
    {
        if (_normalActions.TryGetValue(key, out var havingAction))
        {
            throw new Exception("Key Value Is Having");
        }

        _normalActions.Add(key, action);
        this.WindowStateNormalAction += action;
    }

    public void DelWindowStateNormalAction(string key)
    {
        if (_normalActions.TryGetValue(key, out var action))
        {
            this.WindowStateNormalAction -= action;
            this._normalActions.Remove(key);
        }
        else
        {
            throw new Exception("Not Found Key");
        }
    }

    public void ClearWindowStateNormalAction()
    {
        foreach (var item in _normalActions)
        {
            this.WindowStateNormalAction -= item.Value;
        }
    }

    #endregion

    public static WindowMoveSizeChange MainWindowChangeHelper { get; set; } = new WindowMoveSizeChange();

    #region Normal Windows Get this Helper Class

    public static WindowMoveSizeChange CreateWindowMoveSizeChange() => new WindowMoveSizeChange();

    #endregion


    #region WindowMove_Command

    /// <summary>
    /// Binding MouseLeftButtonDown Event 
    /// </summary>
    /// <param name="sender"></param>
    /// <param name="e"></param>
    /// <param name="mainWindow"></param>
    public void WindowMove_MouseButtonDown(object sender, MouseButtonEventArgs e, Window? mainWindow)
    {
        if (e.ButtonState == MouseButtonState.Pressed)
        {
            mainWindow?.DragMove();
        }
        
        var element = (FrameworkElement)sender;
        if (e.ClickCount == 1)
        {
            var timer = new System.Timers.Timer(500);
            timer.AutoReset = false;
            timer.Elapsed += new ElapsedEventHandler((o, ex) => element.Dispatcher.Invoke(new Action(() =>
            {
                var timer2 = (System.Timers.Timer)element.Tag;
                timer2.Stop();
                timer2.Dispose();
            })));
            timer.Start();
            element.Tag = timer;
        }

        if (e.ClickCount <= 1) return;
        {
            if (element.Tag is not System.Timers.Timer timer) return;
            timer.Stop();
            timer.Dispose();

            if (mainWindow?.WindowState == WindowState.Maximized)
            {
                mainWindow.WindowState = WindowState.Normal;
                this.WindowStateNormalAction?.Invoke();
            }
            else
            {
                mainWindow!.WindowState = WindowState.Maximized;
                this.WindowStateMaximizedAction?.Invoke();
            }
        }
    }

    #endregion
}